package hku.cs.eclunuo.run;

import hku.cs.eclunuo.LunuoConstant;
import hku.cs.eclunuo.LunuoPlugin;
import hku.cs.eclunuo.util.LunuoLibHelper;
import hku.cs.lunuo.constant.DirAndFileConstant;
import hku.cs.lunuo.instrument.Instrument;
import hku.cs.lunuo.instrument.TestCaseInstrument;
import hku.cs.lunuo.profile.PredsProfile;
import hku.cs.lunuo.tools.DirTools;

import java.io.File;
import java.io.FileNotFoundException;
import java.io.IOException;
import java.util.List;

import org.eclipse.core.resources.IProject;
import org.eclipse.core.runtime.IPath;
import org.eclipse.jdt.core.IJavaProject;
import org.eclipse.jdt.core.JavaCore;
import org.eclipse.jdt.core.JavaModelException;

import soot.Scene;
import soot.options.Options;

public class LightRunner {

	private IProject project;

	public LightRunner(IProject project) {
		super();
		this.project = project;
	}

	public void run(List<String> targetLst, List<String> testLst,
			List<String> copyLst, List<String> removeLst) {

		IJavaProject javaProject = JavaCore.create(project);

		IPath metaPjtPath = LunuoPlugin.METADIR.append(javaProject.getProject()
				.getName()
				+ File.separator);
		String classpath = LunuoLibHelper.urlsToString(LunuoLibHelper
				.getSootClassPath(javaProject));
		String output = ".";

		try {
			output = LunuoPlugin.METADIR
					.append(javaProject.getOutputLocation()).toOSString();
		} catch (JavaModelException e1) {
			e1.printStackTrace();
		}

		if (testLst.size() > 0) {
			List<String> rrss;
			int ii = testLst.size() / 10;
			for (int j = 1; j <= ii + 1; j++) {
				if (10 * j - 1 > testLst.size())
					rrss = testLst.subList(10 * (j - 1), testLst.size());
				else
					rrss = testLst.subList(10 * (j - 1), 10 * j - 1);
				soot.G.reset();
				Scene.v().setSootClassPath(classpath);
				try {
					new TestCaseInstrument().modifyTests(rrss
							.toArray(new String[0]), metaPjtPath.toString()
							+ LunuoConstant.INSTRDEFAULTOUTDIR, output);
				} catch (FileNotFoundException e) {
					e.printStackTrace();
				} catch (IOException e) {
					e.printStackTrace();
				}
			}

		}

		if (targetLst.size() > 0) {
			String preoutput = metaPjtPath.append(DirAndFileConstant.PRED)
					.toOSString();
			DirTools.prepare(preoutput);

			List<String> rrss;
			int ii = targetLst.size() / 10;
			for (int j = 1; j <= ii + 1; j++) {
				if (10 * j - 1 >= targetLst.size())
					rrss = targetLst
							.subList(10 * (j - 1), targetLst.size());
				else
					rrss = targetLst.subList(10 * (j - 1), 10 * j - 1);

				soot.G.reset();
				Scene.v().setSootClassPath(classpath);
				Options.v().set_output_dir(output);

				Instrument.main(rrss.toArray(new String[0]));

				soot.G.reset();
				Scene.v().setSootClassPath(classpath);
//				PredsProfile pp = new PredsProfile();
//
//				pp.profile(rrss.toArray(new String[0]), new File(preoutput));
			}

		}

		for (String file : copyLst) {
			File f = LunuoPlugin.METADIR.append(file).toFile();
			if (!f.exists()) {
				File p = project.getWorkspace().getRoot().getLocation().append(
						file).toFile();
				if (p.exists()) {
					if (p.isDirectory())
						f.mkdirs();
					if (p.isFile())
						try {
							DirTools.copy(p, f);
						} catch (Exception e) {
							e.printStackTrace();
						}
				}
			}
		}

		for (String file : removeLst) {
			DirTools.delete(LunuoPlugin.METADIR.append(file).toFile());
		}
	}

}
